<?php

declare(strict_types=1);

namespace App\Model;

use App\Helpers\AliyunUtil;
use App\Helpers\DateUtil;
use Hyperf\DbConnection\Db;
use Hyperf\DbConnection\Model\Model;

/**
 * 动态
 */
class Moment extends Model
{
    protected $table = 'moment';

    //正常
    const STATUS_OK = 1;
    //删除
    const STATUS_DEL = 0;
    //待审核
    const STATUS_VERIFING = -1;
    //审核不通过
    const STATUS_BAD = -2;

    //动态缩略图-大
    const THUMB_SIZE_BIG = 500;
    //动态缩略图-小
    const THUMB_SIZE_SMALL = 250;

    //普通动态
    const TYPE_NORMAL = 1;
    //真人头像分享动态
    const TYPE_REAL_AVATAR_SHARE = 2;
    //爱情宣言动态
    const TYPE_SELF_INTRO = 3;

    protected $fillable = [
        "user_id", "status", "voice", "user_gender", "words", "images", "is_top", "status", "video", 'moment_type'
    ];

    public function userItem()
    {
        return $this->belongsTo(User::class, 'user_id', 'id');
    }

    public function userProfile()
    {
        return $this->belongsTo(UserProfile::class, 'user_id', 'user_id');
    }

    public function setImagesAttribute($images)
    {
        if (is_array($images)) {
            $this->attributes['images'] = json_encode($images);
        }
    }

    public function getImagesAttribute($images)
    {
        return json_decode($images, true);
    }

    /**
     * 获取数据
     */
    static function getItem($momentId = 0)
    {
        return self::find($momentId);
    }

    /**
     * 批量获取数据
     */
    static function getItems($momentIds = 0)
    {
        if (empty($momentIds)) return [];
        $data = self::whereIn('id', $momentIds)->get()->toArray();
        $list = [];
        foreach ($data as $item) $list[$item['id']] = $item;
        return $list;
    }

    /**
     * 获取数据
     */
    static function getList($page = 1, $pageNum = 20, $gender = -1, $orderType = '')
    {
        $where = [
            ['moment.status', self::STATUS_OK],
            ['user.status', User::STATUS_OK],
        ];
        if ($gender > -1) $where[] = ['user_gender', $gender];
        $start = ($page - 1) * $pageNum;
        $selectField = ['moment.*'];
        $query = Db::table('moment')->join('user', function ($join) {
            $join->on('user.id', '=', 'moment.user_id');
        });
        if ($orderType == 'hot') {
            $where[] = ['moment.created_at', '>', date('Y-m-d H:i:s', strtotime('-15 day'))];
            return $query->where($where)->select($selectField)
                ->offset($start)->limit($pageNum)
                ->orderBy('is_top', 'desc')->orderBy('like_num', 'desc')
                ->get()->toArray();
        }
        return $query->where($where)->select($selectField)
            ->offset($start)->limit($pageNum)
            ->orderBy('is_top', 'desc')->orderBy('moment.id', 'desc')
            ->get()->toArray();
    }

    /**
     * 获取数据
     */
    static function getUserList($userId = 0, $page = 1, $pageNum = 20, $gender = -1, $selfUserId = 0)
    {
        $where = [
            'moment.status' => self::STATUS_OK,
        ];
        if ($gender > -1) $where['user_gender'] = $gender;
        $start = ($page - 1) * $pageNum;
        $query = Db::table('moment')->join('user', function ($join) {
            $where = ['user.status' => User::STATUS_OK];
            $join->on('user.id', '=', 'moment.user_id')->where($where);
        });
        $selectField = ['moment.*'];
        if (!is_array($userId)) {
            $userId && $where['user_id'] = $userId;
            $data = $query->where($where)->select($selectField)->offset($start)->limit($pageNum)->orderBy('is_top', 'desc')->orderBy('moment.id', 'desc')->get()->toArray();
        } else {
            $data = $query->where($where)->whereIn('user_id', $userId)->select($selectField)->offset($start)->limit($pageNum)->orderBy('is_top', 'desc')->orderBy('moment.id', 'desc')->get()->toArray();
        }

        $extra = [];
        //全部
        if (
            $userId == 0 ||
            $userId == $selfUserId ||
            (is_array($userId) && in_array($selfUserId, $userId))
        ) {
            $where = [
                'user_id' => $selfUserId,
            ];
            $extra = self::where($where)->whereIn('status', [self::STATUS_VERIFING])->orderBy('id', 'desc')->get()->toArray();
        }
        return ($page == 1 && $extra) ? array_merge($extra, $data) : $data;
    }

    /**
     * 获取图片动态
     */
    static function getImageList($page = 1, $pageNum = 20, $gender = -1)
    {
        $where = [
            ['images', '<>', ''],
            ['status', self::STATUS_OK],
        ];
        if ($gender > -1) $where['user_gender'] = $gender;
        $start = ($page - 1) * $pageNum;
        return self::where($where)->offset($start)->limit($pageNum)->orderBy(Db::raw('rand()'))->get()->toArray();
    }

    /**
     * 封装榜单数据
     */
    static function buildItem($item = [], $userProfile = null, $userId = 0)
    {
        if (!$item || !$userProfile) return [];
        if (!is_array($item)) $item = json_decode(json_encode($item), true);
        if (!is_array($userProfile)) $userProfile = $userProfile->toArray();
        $imageInfo = self::packMomentImages($item['images'], true, $item['moment_type']);
        $ret = [
            'moment_id' => $item['id'],
            'user_id' => $item['user_id'],
            'age' => DateUtil::dateDiff($userProfile['birthday'], date('Y-m-d'), 'Y'),
            'gender' => $userProfile['gender'],
            'nick_name' => $userProfile['nick_name'],
            'avatar' => UserProfile::buildAvatar($userProfile['avatar']),
            'words' => $item['words'],
            'thumb_images' => $imageInfo['thumb_images'],
            'images' => $imageInfo['images'],
            'voice' => self::packMediaInfo($item, 'voice'),
            'video' => self::packMediaInfo($item, 'video'),
            'comment_list' => MomentComment::getList($item['id'], 1, 2, true),
            'pub_time' => (string) $item['created_at'],
            'like_num' => $item['like_num'],
            'comment_num' => $item['comment_num'],
            //是否置顶
            'is_top' => $item['is_top'],
            //动态审核状态
            'status' => $item['status'],
            //动态类型
            'moment_type' => $item['moment_type'],
        ];
        if ($userId) {
            $ret['is_liked'] = MomentLike::check($userId, $item['id']);
            $ret['is_followed'] = $userId == $item['user_id'] ? 1 : UserFollow::check($userId, $item['user_id']);
        }
        return $ret;
    }

    /**
     * 封装图片数组
     * @param array $images
     * @param bool $use_thumb
     * @return array
     */
    static function packMomentImages($images = [], $use_thumb = true, $momentType = 1)
    {
        $ret = ['images' => [], 'thumb_images' => []];
        if ($images) {
            if (is_string($images)) $images = json_decode($images, true);
            $size = count($images) > 1 ? self::THUMB_SIZE_SMALL : self::THUMB_SIZE_BIG;
            foreach ($images as $image) {
                $bigImage = $url = AliyunUtil::IMG_HOST . urlencode($image);
                $thumbImage = !$use_thumb ? $url : AliyunUtil::imageResize($url,  $size, $size);
//                if ($momentType == self::TYPE_REAL_AVATAR_SHARE) {
//                    $thumbImage .= '/watermark,image_cmVhbDIwMjItMDEucG5n';
//                    $bigImage .= '?x-oss-process=image/watermark,image_cmVhbDIwMjItMDEucG5n';
//                }
                $ret['thumb_images'][] = $thumbImage;
                $ret['images'][] = $bigImage;
            }
        }
        return $ret;
    }

    /**
     * 语音数据
     * @param $item
     * @return mixed|null
     */
    static function packMediaInfo($item, $type = 'voice')
    {
        //动态声音
        $voice = $item[$type] ? json_decode($item[$type], true) : null;
        if (isset($voice['link']) && $voice['link']) {
            $voice['link'] = AliyunUtil::VOICE_HOST . $voice['link'];
            $type == 'video'
                && isset($voice['poster'])
                && $voice['poster'] = !$voice['poster'] ? '' : AliyunUtil::imageResize(AliyunUtil::IMG_HOST . $voice['poster'], 500);
        }
        return $voice;
    }

    /**
     * 更新动态评论数量
     */
    static function updateCommentNum($momentId = 0, $commentNum = 1)
    {
        return $commentNum > 0 ?
            self::where('id', $momentId)->limit(1)->increment('comment_num', abs($commentNum)) :
            self::where('id', $momentId)->limit(1)->decrement('comment_num', abs($commentNum));
    }

    /**
     * 更新动态喜欢数量
     */
    static function updateLikeNum($momentId = 0, $commentNum = 1)
    {
        return $commentNum > 0 ?
            self::where('id', $momentId)->limit(1)->increment('like_num', abs($commentNum)) :
            self::where('id', $momentId)->limit(1)->decrement('like_num', abs($commentNum));
    }

    /**
     * 用户发布动态数量
     */
    static function checkCount($userId = 0, $startTime = '')
    {
        $where = [
            ['user_id', $userId],
            // ['status', self::STATUS_VERIFING]
        ];
        if ($startTime) $where[] = ['created_at', '>=', $startTime];
        return self::where($where)->count();
    }

    /**
     * 真人头像分享数量
     */
    static function checkRealAvatar($userId = 0, $offsetLmt = 1800)
    {
        $where = [
            ['user_id', $userId],
            ['moment_type', self::TYPE_REAL_AVATAR_SHARE]
        ];
        if ($offsetLmt) $where[] = ['created_at', '>=', date('Y-m-d H:i:s', time() - $offsetLmt)];
        return self::where($where)->count();
    }

    /**
     * 动态相册
     */
    static function getMomentPics($userId = 0, $limit = 4, $posters = '')
    {
        $where = [
            ['user_id', $userId],
            ['status', Moment::STATUS_OK],
            ['images', '<>', '']
        ];
        $moments = Moment::where($where)->orderBy('id', 'desc')->select(['images'])->limit($limit)->get()->toArray();
        $images = [];
        foreach ($moments as $moment) {
            $images = array_merge($images, Moment::packMomentImages($moment['images'])['thumb_images']);
        }
        //照片墙
        if (empty($images)) {
            $posters = !$posters ? [] : explode(',', $posters);
            foreach ($posters as &$poster) {
                $images[] = AliyunUtil::imageResize(AliyunUtil::IMG_HOST . $poster);
            }
        }
        return $images ?? [];
    }

    /**
     * 视频动态列表
     */
    static function getVideoList($userId = 0)
    {
        $where = [];
        $userId && $where[] = ['user_id', $userId];
        $where[] = ['status', Moment::STATUS_OK];
        $where[] = ['video', '<>', ''];
        $links = Moment::where($where)->orderBy('id', 'desc')->pluck('video')->toArray();
        foreach ($links as &$link) {
            $info = json_decode($link, true);
            $link = AliyunUtil::VOICE_HOST . $info['link'];
        }
        return $links;
    }

    /**
     * 动态类型
     */
    static function getMomentTypeContent($moment = [])
    {
        if ($moment['video']) {
            $info = json_decode($moment['video'], true);
            $link = AliyunUtil::VOICE_HOST . $info['link'];
            return ['type' => 'video', 'content' => $link];
        } elseif ($moment['images']) {
            is_string($moment['images']) && $images = json_decode($moment['images'], true);
            $link = AliyunUtil::imageResize(AliyunUtil::IMG_HOST . $images[0], 200);
            return ['type' => 'image', 'content' => $link];
        } else return ['type' => 'text', 'content' => mb_substr($moment['words'], 0, 20)];
    }
}
